# 导入所需的调度器类和触发器类
from apscheduler.schedulers.background import BackgroundScheduler #后台运行
from apscheduler.schedulers.blocking import BlockingScheduler  #主进程运行，需要单独运行
from apscheduler.triggers.interval import IntervalTrigger #时间间隔
from apscheduler.triggers.cron import CronTrigger #复杂的定时任务
from apscheduler.triggers.date import DateTrigger #一次性定时任务
from django.core.management.base import BaseCommand
from apscheduler import events
from pytz import timezone
from threading import RLock
from datetime import datetime, timedelta
from gs_scheduler.models import SQLiteDB
#定时任务
from .task import example_cron,example_date,example_interval
from .task import delete_apscheduler_history
from .task import send_to_big_data
#日志
from utils.log_util import info_log
from .config import LISTENER
from .config import TIME_ZONE,JOB_DEFAULTS,JOB_STORE

#脚本运行：python manage.py crontab
class Command(BaseCommand):
    TIME_FORMAT = '%Y-%m-%d %H:%M:%S'
    #初始化调度器
    def _scheduler_obj(self):
        scheduler = BlockingScheduler()
        scheduler.configure(
            timezone = TIME_ZONE, #时区
            job_defaults=JOB_DEFAULTS, #job的默认配置
            jobstores=JOB_STORE, #job的存储后端
        )
        return scheduler

    #添加任务
    def _add_job(self,scheduler:BlockingScheduler):
        #每分钟执行一次
        scheduler.add_job(
            send_to_big_data,
            trigger=IntervalTrigger(minutes=5),
            id='send_to_big_data',
            replace_existing=True,
            coalesce=True,
        )

        # 设置每天的11:03:10 执行一次
        scheduler.add_job(
            example_cron,
            trigger=CronTrigger(hour=11, minute=3, second=10),
            id='example_cron',
            replace_existing=True,
            coalesce=True,
        )
        # 设置在2023-08-10 11:03:01执行一次，只执行一次
        scheduler.add_job(
            example_date,
            trigger=DateTrigger(run_date=datetime(2024, 12, 10, 11, 3, 1)),
            id='example_date',
            replace_existing=True,
            coalesce=True,
        )
        #每隔8个小时，清除历史的记录
        scheduler.add_job(
            delete_apscheduler_history,
            trigger=IntervalTrigger(hours=8),
            id='delete_apscheduler_history',
            replace_existing=True,
            coalesce=True,
        )

    #添加监听器
    def _listener(self,event:events):
        code = event.code

        run_time = datetime.now().strftime(self.TIME_FORMAT)
        msg = LISTENER.get(code)
        db = SQLiteDB()
        if msg:
            if code == 4096:
                #成功运行
                job_id = event.job_id
                db.insert_into_apscheduler_history([job_id,run_time,0])
            elif code == 8192:
                #运行异常了
                job_id = event.job_id
                db.insert_into_apscheduler_history([job_id,run_time,1,msg])
                db.conn.commit()
            else:
                info_log(msg)
        db.close()

    #运行
    def handle(self, *args, **options):
        scheduler = self._scheduler_obj()
        #创建记录运行记录
        db = SQLiteDB()
        db.create_apscheduler_history()
        db.close()
        #设置监听器
        scheduler.add_listener(self._listener)
        #设置定时任务
        self._add_job(scheduler)
        try:
            # print('{},定时器启动成功,等待定时任务执行...'.format(datetime.now().strftime(self.TIME_FORMAT)))
            scheduler.start()
        except KeyboardInterrupt:
            scheduler.shutdown()

#伴随django，在后台运行的。
class BackRunScheduler(Command):
    TIME_FORMAT = '%Y-%m-%d %H:%M:%S'
    # 初始化调度器
    def _scheduler_obj(self):
        scheduler = BackgroundScheduler()
        scheduler.configure(
            timezone=TIME_ZONE,  # 时区
            job_defaults=JOB_DEFAULTS,  # job的默认配置
            jobstores=JOB_STORE,  # job的存储后端
        )
        return scheduler
    # 运行
    def start(self, *args, **options):
        scheduler = self._scheduler_obj()
        # 创建记录运行记录
        db = SQLiteDB()
        db.create_apscheduler_history()
        db.close()
        # 设置监听器
        scheduler.add_listener(self._listener)
        # 设置定时任务
        self._add_job(scheduler)
        try:
            # print('{},定时器启动成功,等待定时任务执行...'.format(datetime.now().strftime(self.TIME_FORMAT)))
            scheduler.start()
        except KeyboardInterrupt:
            scheduler.shutdown()